package simulaco.dao;

import gminet.infra.dao.DataAccessObject;
import gminet.infra.db.TransactionException;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

import simulaco.dto.ConcursoNivel;
import simulaco.dto.Materia;
import simulaco.dto.SimuladoModelo;
import simulaco.dto.SimuladoModeloMateria;
import simulaco.dto.Situacao;

public class SimuladoModeloMateriaDAO extends DataAccessObject {

    public static SimuladoModeloMateria findByPK(SimuladoModeloMateria simuladoMateria, Connection conn)
            throws TransactionException {

        SimuladoModelo simulado = simuladoMateria.getSimuladoModelo();
        Materia materia = simuladoMateria.getMateria();
        return findByPK(simulado.getCodigo(), materia.getCodigo(), conn);
    }

    public static SimuladoModeloMateria findByPK(int codigoSimulado, int codigoMateria, Connection conn)
            throws TransactionException {

        StringBuffer sbSql = new StringBuffer();
        sbSql.append("SELECT A.CD_SIMULADO            CD_SIMULADO           ");
        sbSql.append("     , S.CD_INSTITUICAO         CD_INSTITUICAO        ");
        sbSql.append("     , S.CD_ORGAO               CD_ORGAO              ");
        sbSql.append("     , S.TX_INDENTIFICACAO      TX_INDENTIFICACAO     ");
        sbSql.append("     , S.TX_DESCRICAO           TX_DESCRICAO          ");
        sbSql.append("     , S.TX_RESUMO              TX_RESUMO             ");
        sbSql.append("     , S.ID_NIVEL               ID_NIVEL              ");
        sbSql.append("     , S.ID_SITUACAO            ID_SITUACAO_SIMULADO  ");
        sbSql.append("     , S.TS_CADASTRO            TS_CADASTRO_SIMULADO  ");
        sbSql.append("     , A.CD_MATERIA             CD_MATERIA            ");
        sbSql.append("     , M.TX_NOME                TX_NOME_MATERIA       ");
        sbSql.append("     , M.ID_SITUACAO            ID_SITUACAO_MATERIA   ");
        sbSql.append("     , A.NR_QUANT_QUESTOES      NR_QUANT_QUESTOES     ");
        sbSql.append("     , A.TX_COMENTARIO          TX_COMENTARIO         ");
        sbSql.append("  FROM SIMULADO_MODELO_MATERIA A ");
        sbSql.append("     , SIMULADO_MODELO         S ");
        sbSql.append("     , MATERIA                 M ");
        sbSql.append(" WHERE A.CD_SIMULADO = S.CD_SIMULADO ");
        sbSql.append("   AND A.CD_MATERIA  = M.CD_MATERIA  ");
        sbSql.append("   AND A.CD_SIMULADO = ? ");
        sbSql.append("   AND A.CD_MATERIA  = ? ");

        SimuladoModeloMateria simuladoMateria = null;
        try {
            PreparedStatement ps = conn.prepareStatement(sbSql.toString());
            int pos = 1;
            setInt(ps, pos++, codigoSimulado);
            setInt(ps, pos++, codigoMateria);
            ResultSet rs = ps.executeQuery();
            if (rs.next()) {
                simuladoMateria = fromResultSet(rs);
            }
            close(ps);
        } catch (SQLException sqle) {
            throw new TransactionException("SimuladoModeloMateriaDAO.findByPK (" + sqle.getMessage() + ")");
        }
        return simuladoMateria;
    }

    public static List<SimuladoModeloMateria> findBySimulado(int codigoSimulado, Connection conn)
            throws TransactionException {

        StringBuffer sbSql = new StringBuffer();
        sbSql.append("SELECT A.CD_SIMULADO            CD_SIMULADO           ");
        sbSql.append("     , S.CD_INSTITUICAO         CD_INSTITUICAO        ");
        sbSql.append("     , S.CD_ORGAO               CD_ORGAO              ");
        sbSql.append("     , S.TX_INDENTIFICACAO      TX_INDENTIFICACAO     ");
        sbSql.append("     , S.TX_DESCRICAO           TX_DESCRICAO          ");
        sbSql.append("     , S.TX_RESUMO              TX_RESUMO             ");
        sbSql.append("     , S.ID_NIVEL               ID_NIVEL              ");
        sbSql.append("     , S.ID_SITUACAO            ID_SITUACAO_SIMULADO  ");
        sbSql.append("     , S.TS_CADASTRO            TS_CADASTRO_SIMULADO  ");
        sbSql.append("     , A.CD_MATERIA             CD_MATERIA            ");
        sbSql.append("     , M.TX_NOME                TX_NOME_MATERIA       ");
        sbSql.append("     , M.ID_SITUACAO            ID_SITUACAO_MATERIA   ");
        sbSql.append("     , A.NR_QUANT_QUESTOES      NR_QUANT_QUESTOES     ");
        sbSql.append("     , A.TX_COMENTARIO          TX_COMENTARIO         ");
        sbSql.append("  FROM SIMULADO_MODELO_MATERIA A ");
        sbSql.append("     , SIMULADO_MODELO         S ");
        sbSql.append("     , MATERIA                 M ");
        sbSql.append(" WHERE A.CD_SIMULADO = S.CD_SIMULADO ");
        sbSql.append("   AND A.CD_MATERIA  = M.CD_MATERIA  ");
        sbSql.append("   AND A.CD_SIMULADO = ? ");

        List<SimuladoModeloMateria> simuladoMateriasList = new ArrayList<SimuladoModeloMateria>(100);
        try {
            PreparedStatement ps = conn.prepareStatement(sbSql.toString());
            setInt(ps, 1, codigoSimulado);
            ResultSet rs = ps.executeQuery();
            while (rs.next()) {
                SimuladoModeloMateria simuladoMateria = fromResultSet(rs);
                simuladoMateriasList.add(simuladoMateria);
            }
            close(rs);
        } catch (SQLException sqle) {
            throw new TransactionException("SimuladoModeloMateriaDAO.findBySimulado (" + sqle.getMessage() + ")");
        }
        return simuladoMateriasList;
    }

    public static List<SimuladoModeloMateria> findByMateria(int codigoMateria, Connection conn)
            throws TransactionException {

        StringBuffer sbSql = new StringBuffer();
        sbSql.append("SELECT A.CD_SIMULADO            CD_SIMULADO           ");
        sbSql.append("     , S.CD_INSTITUICAO         CD_INSTITUICAO        ");
        sbSql.append("     , S.CD_ORGAO               CD_ORGAO              ");
        sbSql.append("     , S.TX_INDENTIFICACAO      TX_INDENTIFICACAO     ");
        sbSql.append("     , S.TX_DESCRICAO           TX_DESCRICAO          ");
        sbSql.append("     , S.TX_RESUMO              TX_RESUMO             ");
        sbSql.append("     , S.ID_NIVEL               ID_NIVEL              ");
        sbSql.append("     , S.ID_SITUACAO            ID_SITUACAO_SIMULADO  ");
        sbSql.append("     , S.TS_CADASTRO            TS_CADASTRO_SIMULADO  ");
        sbSql.append("     , A.CD_MATERIA             CD_MATERIA            ");
        sbSql.append("     , M.TX_NOME                TX_NOME_MATERIA       ");
        sbSql.append("     , M.ID_SITUACAO            ID_SITUACAO_MATERIA   ");
        sbSql.append("     , A.NR_QUANT_QUESTOES      NR_QUANT_QUESTOES     ");
        sbSql.append("     , A.TX_COMENTARIO          TX_COMENTARIO         ");
        sbSql.append("  FROM SIMULADO_MODELO_MATERIA A ");
        sbSql.append("     , SIMULADO_MODELO         S ");
        sbSql.append("     , MATERIA                 M ");
        sbSql.append(" WHERE A.CD_SIMULADO = S.CD_SIMULADO ");
        sbSql.append("   AND A.CD_MATERIA  = M.CD_MATERIA  ");
        sbSql.append("   AND A.CD_MATERIA  = ? ");

        List<SimuladoModeloMateria> simuladoMateriasList = new ArrayList<SimuladoModeloMateria>(100);
        try {
            PreparedStatement ps = conn.prepareStatement(sbSql.toString());
            int pos = 1;
            setInt(ps, pos++, codigoMateria);
            ResultSet rs = ps.executeQuery();
            while (rs.next()) {
                SimuladoModeloMateria simuladoMateria = fromResultSet(rs);
                simuladoMateriasList.add(simuladoMateria);
            }
            close(rs);
        } catch (SQLException sqle) {
            throw new TransactionException("SimuladoModeloMateriaDAO.findByMateria (" + sqle.getMessage() + ")");
        }
        return simuladoMateriasList;
    }

    public static void insert(SimuladoModeloMateria simuladoMateria, Connection conn) throws TransactionException {

        StringBuffer sbSql = new StringBuffer();
        sbSql.append("INSERT INTO SIMULADO_MODELO_MATERIA ");
        sbSql.append("     ( CD_SIMULADO       ");
        sbSql.append("     , CD_MATERIA        ");
        sbSql.append("     , NR_QUANT_QUESTOES ");
        sbSql.append("     , TX_COMENTARIO     ");
        sbSql.append(") VALUES (?,?,?,?)       ");

        try {
            PreparedStatement ps = conn.prepareStatement(sbSql.toString());
            int pos = 1;
            setInt(ps, pos++, simuladoMateria.getSimuladoModelo().getCodigo());
            setInt(ps, pos++, simuladoMateria.getMateria().getCodigo());
            setInt(ps, pos++, simuladoMateria.getQuantidadeQuestoes());
            setString(ps, pos++, simuladoMateria.getComentarioMateria(), true);
            ps.executeUpdate();
            close(ps);
        } catch (SQLException sqle) {
            throw new TransactionException("SimuladoModeloMateriaDAO.insert (" + sqle.getMessage() + ")");
        }

    }

    public static void update(SimuladoModeloMateria simuladoMateria, Connection conn) throws TransactionException {

        StringBuffer sbSql = new StringBuffer();
        sbSql.append("UPDATE SIMULADO_MODELO_MATERIA ");
        sbSql.append("   SET NR_QUANT_QUESTOES = ? ");
        sbSql.append("     , TX_COMENTARIO     = ? ");
        sbSql.append(" WHERE CD_SIMULADO       = ? ");
        sbSql.append("   AND CD_MATERIA        = ? ");

        try {
            PreparedStatement ps = conn.prepareStatement(sbSql.toString());
            int pos = 1;
            setInt(ps, pos++, simuladoMateria.getQuantidadeQuestoes());
            setString(ps, pos++, simuladoMateria.getComentarioMateria(), true);
            setInt(ps, pos++, simuladoMateria.getSimuladoModelo().getCodigo());
            setInt(ps, pos++, simuladoMateria.getMateria().getCodigo());
            ps.executeUpdate();
            close(ps);
        } catch (SQLException sqle) {
            throw new TransactionException("SimuladoUsuarioQuestaoDAO.update (" + sqle.getMessage() + ")");
        }
    }

    public static void delete(SimuladoModeloMateria simuladoMateria, Connection conn) throws TransactionException {

        StringBuffer sbSql = new StringBuffer();
        sbSql.append("DELETE FROM SIMULADO_MODELO_MATERIA  ");
        sbSql.append(" WHERE CD_SIMULADO = ? ");
        sbSql.append("   AND CD_MATERIA  = ? ");

        try {
            PreparedStatement ps = conn.prepareStatement(sbSql.toString());
            int pos = 1;
            setInt(ps, pos++, simuladoMateria.getSimuladoModelo().getCodigo());
            setInt(ps, pos++, simuladoMateria.getMateria().getCodigo());
            ps.executeUpdate();
            close(ps);
        } catch (SQLException sqle) {
            throw new TransactionException("SimuladoModeloMateriaDAO.delete (" + sqle.getMessage() + ")");
        }
    }

    public static void deleteBySimulado(SimuladoModelo simulado, Connection conn) throws TransactionException {

        StringBuffer sbSql = new StringBuffer();
        sbSql.append("DELETE FROM SIMULADO_MODELO_MATERIA  ");
        sbSql.append(" WHERE CD_SIMULADO = ? ");
        try {
            PreparedStatement ps = conn.prepareStatement(sbSql.toString());
            setInt(ps, 1, simulado.getCodigo());
            ps.executeUpdate();
            close(ps);
        } catch (SQLException sqle) {
            throw new TransactionException("SimuladoModeloMateriaDAO.deleteBySimulado (" + sqle.getMessage() + ")");
        }
    }

    private static SimuladoModeloMateria fromResultSet(ResultSet rs) throws SQLException {

        // SIMULADO MATERIA
        SimuladoModeloMateria simuladoMateria = new SimuladoModeloMateria();
        // SIMULADO
        SimuladoModelo simulado = new SimuladoModelo();
        simulado.setCodigo(getInt(rs, "CD_SIMULADO"));
        simulado.getInstituicao().setCodigo(getInt(rs, "CD_INSTITUICAO"));
        simulado.getOrgao().setCodigo(getInt(rs, "CD_ORGAO"));
        simulado.setIdentificacao(getString(rs, "TX_INDENTIFICACAO"));
        simulado.setDescricao(getString(rs, "TX_DESCRICAO"));
        simulado.setResumo(getString(rs, "TX_RESUMO"));
        simulado.setNivel(ConcursoNivel.getNivelById(getByte(rs, "ID_NIVEL")));
        simulado.setSituacao(Situacao.getSituacaoById(getByte(rs, "ID_SITUACAO_SIMULADO")));
        simulado.setDataCadastro(getDateFromTimestamp(rs, "TS_CADASTRO_SIMULADO"));
        simuladoMateria.setSimuladoModelo(simulado);
        // MATERIA
        Materia materia = new Materia();
        materia.setCodigo(getInt(rs, "CD_MATERIA"));
        materia.setNome(getString(rs, "TX_NOME_MATERIA"));
        materia.setSituacao(Situacao.getSituacaoById(getByte(rs, "ID_SITUACAO_MATERIA")));
        simuladoMateria.setMateria(materia);
        //
        simuladoMateria.setQuantidadeQuestoes(getInt(rs, "NR_QUANT_QUESTOES"));
        simuladoMateria.setComentarioMateria(getString(rs, "TX_COMENTARIO"));
        //
        return simuladoMateria;
    }

}
